//  File:         User.cpp
//  Author:       Scott Nordmann & Lauren Wallace
//  Description:  Non-inline member function definitions.
#include "Date.h"
#include "Entry.h"
#include "User.h"
#include "TagSpec.h"
#include "Tag.h"
#include <string>
#include <iostream>
#include <fstream>


using namespace std;

User::User()
{
	notebook      = new Notebook;
	toDoList      = new ToDoList;
	calendar      = new Calendar;
	inbox         = new Inbox;
	tagCollection = new TagCollection;
}
User::User(const string& u, const string& pwd, ifstream& ifsave)
{
	setUsername(u);
	setPassword(pwd);

	notebook      = new Notebook(ifsave);
	toDoList      = new ToDoList(ifsave);
	calendar      = new Calendar(ifsave);
	tagCollection = new TagCollection;
	populateTagCollection(ifsave);
	inbox         = new Inbox(ifsave);
	
}
User::~User()
{	
	delete notebook;
	delete calendar;
	delete toDoList;
	delete tagCollection;
}

void User::shutDown(std::ofstream& ofsave)
{
	notebook->		shutDown(ofsave);
	toDoList->		shutDown(ofsave);
	calendar->		shutDown(ofsave);
	tagCollection->	shutDown(ofsave);
	inbox->			shutDown(ofsave);
	delete this;
}
void User::populateTagCollection(ifstream& ifsave)
{
	int numSpecs = 0;
	int numTags = 0;
	int specCtr = 0;
	int tagCtr = 0;

	TagSpec* tempSpec;
	Tag* tempTag;

	string tempName; 
	string tempEntry;
	string tempType;
	
	ifsave >> numSpecs;
	ifsave.ignore();
	while (specCtr != numSpecs)
	{
		//create the tagspec
		++specCtr;
		getline(ifsave, tempName);
		tempSpec = ( tagCollection->createTagSpec(tempName) );
		//make the halftags and send them to the entries to be completed
		tagCtr=0;
		ifsave >> numTags;
		ifsave.ignore();
		while (tagCtr != numTags)
		{
			++tagCtr;
			tempTag = tagCollection->createHalfTag(*tempSpec);
			getline(ifsave,tempType);

			if (tempType == "Note")
			{
				getline(ifsave,tempEntry);
				notebook->tagNote(*tempTag, tempEntry);
			}
			else if (tempType == "Task")
			{
				getline(ifsave,tempEntry);
				toDoList->tagTask(*tempTag, tempEntry);
			}
			else if (tempType == "Event")
			{
				string dateString;
				getline(ifsave, tempType);

				getline(ifsave,tempEntry);

				calendar->tagEvent(*tempTag, dateString, tempEntry);
			}
		}
	}
}

void User::display()const
{
	cout << "Username: " << getUsername() << endl;
	cout << "Password: " << getPassword() << endl;
}

void User::populate()
{
	string temp;
	
	cout << "Enter User Name: ";
	getline(cin, temp);
	setUsername(temp);

	cout << "Enter " << temp << "'s password: ";
	getline(cin, temp);
	setPassword(temp);	
}

void User::viewNotebook()
{
	notebook->display();
}

void User::viewCalendar()
{
	calendar->display();
}

void User::viewToDoList()
{
	toDoList->display();
}

void User::viewByTag()
{
	tagCollection->displayByTag();
}

void User::createEvent()
{	
	calendar->createEvent(getUsername());
}

void User::deleteEvent()
{
	calendar->deleteEvent();
}

void User::createNote()
{
	notebook->createNote(getUsername() ) ;
}

void User::createTask()
{
	toDoList->createTask(getUsername() );
}

void User::createTag()
{
	Tag* currentTag;
	bool tagged=true;
	currentTag = ( tagCollection->tagEntry() );
	char command = ' ';

	if (currentTag != NULL)
	{
		while (toupper(command) != 'Q')
		{
			cout << "What would you like to tag?" << endl << endl;

			cout << "N: a Note from your Notebook" << endl;
			cout << "T: a Task from the To-Do List" << endl;
			cout << "E: an Event from the Calendar" << endl;
			cout << "Q: Quit" << endl << endl;
			
			cout << "Please enter your selection: ";
			cin >> command;
			cin.ignore();

			switch (toupper(command))
			{
			case 'N':
				if (notebook->isEmpty())
					cout << "You have no notes.";
				else
				{
				tagged=notebook->tagNote(*currentTag);
				command='Q';
				}
				break;
			
			case 'T':
				if (toDoList->isEmpty())
					cout << "You have no tasks.";
				else
				{
				tagged=toDoList->tagTask(*currentTag);
				command='Q';
				}
				break;
			
			case 'E':
				if (calendar->isEmpty())
					cout << "You have no events.";
				else
				{
				tagged=calendar->tagEvent(*currentTag);
				command='Q';
				}
				break;
			
			case 'Q':
				tagged=false;
				break;

			default:
				cout << "Invalid selection." << endl << endl;
				break;
			}

			system("cls");
		}
		if (!tagged)
		{
			tagCollection->removeHalfTag(*currentTag);
		}
	}
}

void User::editEvent()
{
	calendar->editEvent();
}

void User::sendMail()
{
	Entry* mail;
	char command = ' ';

	while (toupper(command) != 'Q')
	{
		cout << "What type of entry would you like to send?" << endl << endl;

		cout << "N: a Note " << endl;
		cout << "T: a Task " << endl;
		cout << "E: an Event " << endl;
		cout << "Q: Quit" << endl << endl;
		
		cout << "Please enter your selection: ";
		cin >> command;
		cin.ignore();

		system("cls");

		switch (toupper(command))
		{
		case 'N':
			mail = notebook->createMail(getUsername());
			inbox->sendMail(mail);
			break;
		
		case 'T':
			mail = toDoList->createMail(getUsername());
			inbox->sendMail(mail);
			break;
		
		case 'E':
			mail = calendar->createMail(getUsername());
			inbox->sendMail(mail);
			break;
		
		case 'Q':
			break;

		default:
			cout << "Invalid selection." << endl << endl;
			break;
		}

		cout << "Press any key to continue . . .";

		cin.ignore();
		cin.get();

		system("cls");
	}
}

void User::checkMail()
{
	vector<Entry*> mail;

	mail = *inbox->checkMail();

	vector<Entry*>::iterator iter;
	for (iter = mail.begin(); iter != mail.end(); ++iter)
	{
		if      (dynamic_cast<Task*>  (*iter) )
			toDoList->createTask(dynamic_cast<Task*>(*iter));
		else if (dynamic_cast<Event*> (*iter) )
			calendar->createEvent(dynamic_cast<Event*>(*iter));
		else 
			notebook->createNote(dynamic_cast<Note*>(*iter));
	}

	inbox->getReceived()->clear();
}

vector<Entry*>* User::getSentMail()
{
	return inbox->getSent();
}

vector<Entry*>* User::getInbox()
{
	return inbox->getReceived();
}

